﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.IO;
using System.Windows.Forms;
using Newtonsoft.Json;
using System.Xml;
using System.Net.Http;
using System.Net.Http.Headers;
using System.Threading;
using System.Net;
using System.Reflection;
using System.Drawing;
using System.Security.Cryptography;

namespace SearchFileIformation
{
    
    
    class SearchFile
    {
        public delegate void SearchFileEvent(object sender, SearchFileEventArgs e);
        public delegate void GetResponseJsonEvent(object sender, SearchFileEventArgs e);
        public SearchFileEvent searchFileEvent;
        public GetResponseJsonEvent getResponseJsonEvent;
        log4net.ILog log = log4net.LogManager.GetLogger("Logger");
        int count = 1;
        public string[] Search(string pathText)
        {
            string[] ans = null;
            count = 1;
            try
            {
                ans = Directory.GetFiles(@pathText, "*Controller.java", System.IO.SearchOption.AllDirectories);
            }
            catch (Exception ex)
            {
                log.Error(this, ex);
                SearchFileEventArgs e = new SearchFileEventArgs(null, ex, count++);
                searchFileEvent(this, e);
            }
            return ans;
        }
        public void RunSearch(object sender)
        {
            try
            {
                string[] allFile = Search(sender.ToString());
                foreach (string file in allFile)
                {
                    ShowResult(file);
                }
                SearchFileEventArgs e = new SearchFileEventArgs("end");
                getResponseJsonEvent(this, e);
            }
            catch(Exception e)
            {
                log.Error(this, e);
                SearchFileEventArgs ex = new SearchFileEventArgs(null, e, count++);
                searchFileEvent(this, ex);
            }           
        }
        
        public void ShowResult(string filePath)
        {
            List<Dictionary<string, string>> file = new List<Dictionary<string, string>>();
            ApiObject apiObject = new ApiObject();            
            Type apiType = apiObject.GetType();
            PropertyInfo[] apiProperty = apiType.GetProperties();
            string[] api = new string[apiProperty.Length];
            int time = 0;
            foreach (PropertyInfo item in apiProperty)
            {
                api[time++]=item.Name;
            }

            string _public = "public";
            Directory.CreateDirectory(Application.StartupPath + "\\TestApiResult");
            StreamWriter sw = new StreamWriter(Application.StartupPath + "\\TestApiResult\\testapitimedata" +
                    DateTime.Now.ToString("yyyy-MM-dd") + ".csv", true);
            sw.Close();
            try
            {
                int fileLength = File.ReadAllLines(filePath).Length;
                string fileAll = File.ReadAllText(filePath);
                string[] contentFound = fileAll.Replace("\r\n", " ").Split(' ');
                string flagClassName = "";
                string getAddress = "@RequestMapping(";
                int flagPos = 0;
                for (int i = 0; i < contentFound.Length; i++)    //找到类名并存储
                {
                    if (contentFound[i].CompareTo("class") == 0)
                    {
                        flagClassName = contentFound[i + 1];
                        flagPos = i;
                        break;
                    }
                }
                string rootAddress = "";     //定义根地址
                if (contentFound[flagPos - 2].Length > getAddress.Length)   //判断是否有根地址，如有则更新根地址
                {
                    rootAddress = contentFound[flagPos - 2].Remove(0, getAddress.Length);
                    rootAddress = ClearDoubleBlankCurves(rootAddress);
                }
                for (int i = flagPos + 1; i < contentFound.Length - 1; i++)
                {
                    if (contentFound[i].CompareTo(_public) == 0)
                    {
                        Dictionary<string, string> fileSub = new Dictionary<string, string>();
                        fileSub.Add(api[5], flagClassName); //将类名映射存入
                        int flagPosMethodStart = 0;
                        for (int k = i; k > flagPos; k--)
                        {
                            if (contentFound[k].StartsWith(getAddress))
                            {
                                flagPosMethodStart = k;
                                break;
                            }
                        }
                        string leafAddress = "";    //定义叶地址
                        if (contentFound[flagPosMethodStart + 1].CompareTo("=") == 0)
                        {
                            leafAddress = contentFound[flagPosMethodStart + 2];
                            leafAddress = ClearDoubleBlankCurves(leafAddress);
                            if (leafAddress.EndsWith(api[1]))
                            {
                                int remove = leafAddress.IndexOf(api[1]);
                                leafAddress = leafAddress.Remove(remove - 1);

                            }
                        }
                        else
                        {
                            if (flagPosMethodStart != 0)
                            {
                                leafAddress = contentFound[flagPosMethodStart].Remove(0, getAddress.Length);
                                leafAddress = ClearDoubleBlankCurves(leafAddress);
                                if (leafAddress.EndsWith(api[1]))
                                {
                                    int remove = leafAddress.IndexOf(api[1]);
                                    leafAddress = leafAddress.Remove(remove - 1);

                                }
                            }
                        }
                        
                        fileSub.Add(api[0], rootAddress + leafAddress.Replace(",", "").Replace(".html",""));    //将根地址和叶地址组合放入字典中
                        bool whetherMethod = false;
                        for (int k = flagPosMethodStart; k < i; k++)
                        {
                            if (contentFound[k].EndsWith(api[1]))
                            {
                                whetherMethod = true;
                                flagPosMethodStart = k;
                            }
                        }
                        //判断是否有method，如有,则这个字符串后的第二个为所需的字符串
                        if (whetherMethod)
                        {
                            if(contentFound[flagPosMethodStart + 2].EndsWith("="))
                                fileSub.Add(api[1], contentFound[flagPosMethodStart + 3].Replace(')', ' '));
                            else
                                fileSub.Add(api[1], contentFound[flagPosMethodStart + 2].Replace(')', ' '));
                        }             
                        else
                            fileSub.Add(api[1], "");       //如果没有method，则为空     
                        //将description的映射存入
                        for (int k = i - 1; k > flagPos; k--)
                        {
                            if (contentFound[k].CompareTo(" ") > 0)
                            {
                                fileSub.Add(api[2], contentFound[k].Replace('"', ' ').Replace(")", ""));
                                break;
                            }
                        }
                        bool flagReturn = true;
                        string judgeWhetherReturn = contentFound[i + 1];
                        if (judgeWhetherReturn.EndsWith("){"))
                        {
                            fileSub.Add(api[3], "");
                            flagReturn = false;
                        }
                        else
                        {
                            fileSub.Add(api[3], contentFound[i + 1]);   //将返回类型的映射存入
                        }

                        int j = i;
                        if (contentFound[i + 1].CompareTo("String") != 0 && flagReturn)
                        {
                            while (j < contentFound.Length)        //找到当前一组数据的param中最后一个字符串的下标
                            {
                                if (contentFound[j].CompareTo("throws") == 0)
                                    break;
                                j++;
                                if (contentFound[j - 1].EndsWith("){"))
                                    break;
                            }
                            string tempParam = "";
                            for (int k = i + 2; k < j; k++)   //将param中各个部分字符串连接起来
                            {
                                tempParam += contentFound[k] + ' ';
                            }
                            tempParam = DeleBracket(tempParam);
                            if (tempParam.EndsWith(")"))
                                tempParam=tempParam.Remove(tempParam.Length - 1, 1);
                            fileSub.Add(api[4], tempParam);
                        }
                        else
                        {
                            if (!flagReturn)
                                fileSub.Add(api[4], "");
                            else
                            {
                                while (j < contentFound.Length)        //找到当前一组数据的param中最后一个字符串的下标
                                {
                                    if (contentFound[j].Length != 0)
                                        if (contentFound[j].EndsWith(")") && !contentFound[j].StartsWith("@") || contentFound[j].EndsWith("){"))
                                            break;
                                    j++;
                                }
                                string tempParam = "";
                                
                                for (int k = i + 1; k <= j; k++)   //将param中各个部分字符串连接起来
                                {
                                    tempParam += contentFound[k] + ' ';
                                }
                                tempParam = DeleBracket(tempParam);
                                if (tempParam.EndsWith(")"))
                                    tempParam = tempParam.Remove(tempParam.Length - 1, 1);
                                fileSub.Add(api[4], tempParam);
                            }
                        }
                        fileSub.Add(api[6], "");
                        fileSub.Add(api[7], "");
                        fileSub.Add(api[8], "");
                        file.Add(fileSub);              //将一组数据的映射存入list
                    }
                }
                foreach (Dictionary<string, string> show in file)
                {
                    ApiObject myApiObject = new ApiObject();
                    Type myApiType = myApiObject.GetType();
                    PropertyInfo[] property = myApiType.GetProperties();
                    foreach(PropertyInfo item in property)
                    {
                        item.SetValue(myApiObject, show[item.Name]);
                        
                    }
                    Thread.Sleep(50);
                    SearchFileEventArgs e = new SearchFileEventArgs(myApiObject, null, file.Count);
                    searchFileEvent(this, e);
                }
                
            }
            catch (Exception e)
            {
                SearchFileEventArgs ex = new SearchFileEventArgs(null, e, count++);
                searchFileEvent(this, ex);
            }
        }
        public string DeleBracket(string str)   //将字符串中的括号及括号以外的字符删除
        {
            int flagPos = 0;
            for (int i = 0; i < str.Length; i++)
            {
                if (str[i] == '(')
                {
                    flagPos = i;
                    break;
                }
            }
            string temp = str.Remove(0, flagPos + 1);
            int len = temp.Length;
            if (temp.EndsWith("){ "))
                return temp.Remove(len -3);
            else
                return temp.Remove(len -2);
        }
        public string ClearDoubleBlankCurves(string str)   //清除字符中的双引号、空格、小括号
        {
            return str.Replace('(', ' ').Replace(')', ' ').Replace('"', ' ').Replace(" ", "");
        }
        public string GetApiFinalName(string api)
        {
            string ret = api.Replace('/', '-').Replace(":", "");
            return ret;
        }
    }
}
